{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<img src=\"https://raw.githubusercontent.com/Qiskit/qiskit-tutorials/master/images/qiskit-heading.png\" width=\"500 px\" align=\"center\">"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## _*Quantum Fourier Transform*_ \n",
    "\n",
    "This notebook is based on an official notebook by Qiskit team, available at https://github.com/qiskit/qiskit-tutorial under the [Apache License 2.0](https://github.com/Qiskit/qiskit-tutorial/blob/master/LICENSE) license. \n",
    "Initially done by Anna Phan.\n",
    "\n",
    "In this tutorial, we [introduce](#introduction) the quantum fourier transform (QFT), [derive](#circuit) the circuit, QASM and Qiskit code, before [implementing](#implementation) it using the simulator and five qubit device."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Introduction <a id='introduction'></a>\n",
    "\n",
    "The Fourier transform occurs in many different versions throughout classical computing, in areas ranging from signal processing to data compression to complexity theory. The quantum Fourier transform (QFT) is the quantum implementation of the discrete Fourier transform over the amplitudes of a wavefunction. It is part of many quantum algorithms, most notably Shor's factoring algorithm and quantum phase estimation. "
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "The discrete Fourier transform acts on a vector $(x_0, ..., x_{N-1})$ and maps it to the vector $(y_0, ..., y_{N-1})$ according to the formula\n",
    "$$y_k = \\frac{1}{\\sqrt{N}}\\sum_{j=0}^{N-1}x_j\\omega_N^{jk}$$\n",
    "where $\\omega_N^{jk} = e^{2\\pi i \\frac{jk}{N}}$.\n",
    "\n",
    "Similarly, the quantum Fourier transform acts on a quantum state $\\sum_{i=0}^{N-1} x_i \\vert i \\rangle$ and maps it to the quantum state $\\sum_{i=0}^{N-1} y_i \\vert i \\rangle$ according to the formula\n",
    "$$y_k = \\frac{1}{\\sqrt{N}}\\sum_{j=0}^{N-1}x_j\\omega_N^{jk}$$\n",
    "with $\\omega_N^{jk}$ defined as above. Note that only the amplitudes of the state were affected by this transformation.\n",
    "\n",
    "This can also be expressed as the map:\n",
    "$$\\vert x \\rangle \\mapsto \\frac{1}{\\sqrt{N}}\\sum_{y=0}^{N-1}\\omega_N^{xy} \\vert y \\rangle$$\n",
    "\n",
    "Or the unitary matrix:\n",
    "$$ U_{QFT} = \\frac{1}{\\sqrt{N}} \\sum_{x=0}^{N-1} \\sum_{y=0}^{N-1} \\omega_N^{xy} \\vert y \\rangle \\langle x \\vert$$"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Circuit and Code <a id='circuit'></a>\n",
    "\n",
    "We've actually already seen the quantum Fourier transform for when $N = 2$, it is the Hadamard operator ($H$):\n",
    "$$H = \\frac{1}{\\sqrt{2}}\\begin{bmatrix} 1 & 1 \\\\ 1 & -1 \\end{bmatrix}$$\n",
    "Suppose we have the single qubit state $\\alpha \\vert 0 \\rangle + \\beta \\vert 1 \\rangle$, if we apply the $H$ operator to this state, we obtain the new state:\n",
    "$$\\frac{1}{\\sqrt{2}}(\\alpha + \\beta) \\vert 0 \\rangle + \\frac{1}{\\sqrt{2}}(\\alpha - \\beta)  \\vert 1 \\rangle \n",
    "\\equiv \\tilde{\\alpha}\\vert 0 \\rangle + \\tilde{\\beta}\\vert 1 \\rangle$$\n",
    "Notice how the Hadamard gate performs the discrete Fourier transform for $N = 2$ on the amplitudes of the state. "
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "So what does the quantum Fourier transform look like for larger N? Let's derive a circuit for $N=2^n$, $QFT_N$ acting on the state $\\vert x \\rangle = \\vert x_1...x_n \\rangle$ where $x_1$ is the most significant bit.\n",
    "\n",
    "\\begin{aligned}\n",
    "QFT_N\\vert x \\rangle & = \\frac{1}{\\sqrt{N}} \\sum_{y=0}^{N-1}\\omega_N^{xy} \\vert y \\rangle \\\\\n",
    "& = \\frac{1}{\\sqrt{N}} \\sum_{y=0}^{N-1} e^{2 \\pi i xy / 2^n} \\vert y \\rangle \\:\\text{since}\\: \\omega_N^{xy} = e^{2\\pi i \\frac{xy}{N}} \\:\\text{and}\\: N = 2^n\\\\\n",
    "& = \\frac{1}{\\sqrt{N}} \\sum_{y=0}^{N-1} e^{2 \\pi i \\left(\\sum_{k=1}^n y_k/2^k\\right) x} \\vert y_1 ... y_n \\rangle \\:\\text{rewriting in fractional binary notation}\\: y = y_1...y_k, y/2^n = \\sum_{k=1}^n y_k/2^k \\\\\n",
    "& = \\frac{1}{\\sqrt{N}} \\sum_{y=0}^{N-1} \\prod_{k=0}^n e^{2 \\pi i x y_k/2^k } \\vert y_1 ... y_n \\rangle \\:\\text{after expanding the exponential of a sum to a product of exponentials} \\\\\n",
    "& = \\frac{1}{\\sqrt{N}} \\bigotimes_{k=1}^n  \\left(\\vert0\\rangle + e^{2 \\pi i x /2^k } \\vert1\\rangle \\right) \\:\\text{after rearranging the sum and products, and expanding} \\\\\n",
    "& = \\frac{1}{\\sqrt{N}} \\left(\\vert0\\rangle + e^{2 \\pi i[0.x_n]} \\vert1\\rangle\\right) \\otimes...\\otimes  \\left(\\vert0\\rangle + e^{2 \\pi i[0.x_1.x_2...x_{n-1}.x_n]} \\vert1\\rangle\\right) \\:\\text{as}\\: e^{2 \\pi i x/2^k} = e^{2 \\pi i[0.x_k...x_n]} \n",
    "\\end{aligned}\n",
    "\n",
    "This is a very useful form of the QFT for $N=2^n$ as only the last qubit depends on the the\n",
    "values of all the other input qubits and each further bit depends less and less on the input qubits. Furthermore, note that $e^{2 \\pi i.0.x_n}$ is either $+1$ or $-1$, which resembles the Hadamard transform.\n",
    "\n",
    "For the QFT circuit, together with the Hadamard gate, we will also need the controlled phase rotation gate, as defined in [OpenQASM](https://github.com/Qiskit/openqasm), to implement the dependencies between the bits:\n",
    "$$CU_1(\\theta) =\n",
    "\\begin{bmatrix} 1 & 0 & 0 & 0 \\\\ 0 & 1 & 0 & 0 \\\\ 0 & 0 & 1 & 0 \\\\ 0 & 0 & 0 & e^{i\\theta}\\end{bmatrix}$$"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Before we create the circuit code for general $N=2^n$, let's look at $N=8,n=3$:\n",
    "$$QFT_8\\vert x_1x_2x_3\\rangle = \\frac{1}{\\sqrt{8}} \\left(\\vert0\\rangle + e^{2 \\pi i[0.x_3]} \\vert1\\rangle\\right) \\otimes \\left(\\vert0\\rangle + e^{2 \\pi i[0.x_2.x_3]} \\vert1\\rangle\\right) \\otimes  \\left(\\vert0\\rangle + e^{2 \\pi i[0.x_1.x_2.x_3]} \\vert1\\rangle\\right) $$\n",
    "\n",
    "The steps to creating the circuit for $\\vert y_1y_2x_3\\rangle = QFT_8\\vert x_1x_2x_3\\rangle$ would be:\n",
    "1. Apply a Hadamard to $\\vert x_3 \\rangle$, giving the state $\\frac{1}{\\sqrt{2}}\\left(\\vert0\\rangle + e^{2 \\pi i.0.x_3} \\vert1\\rangle\\right) = \\frac{1}{\\sqrt{2}}\\left(\\vert0\\rangle + (-1)^{x_3} \\vert1\\rangle\\right)$\n",
    "2. Apply a Hadamard to $\\vert x_2 \\rangle$, then depending on $k_3$ (before the Hadamard gate) a $CU_1(\\frac{\\pi}{2})$, giving the state $\\frac{1}{\\sqrt{2}}\\left(\\vert0\\rangle + e^{2 \\pi i[0.x_2.x_3]} \\vert1\\rangle\\right)$\n",
    "3. Apply a Hadamard to $\\vert x_1 \\rangle$, then $CU_1(\\frac{\\pi}{2})$ depending on $k_2$, and $CU_1(\\frac{\\pi}{4})$ depending on $k_3$.\n",
    "4. Measure the bits in reverse order, that is $y_3 = x_1, y_2 = x_2, y_1 = y_3$.\n",
    "\n",
    "In the Quantum Experience composer (if controlled phase rotation gates were available) this circuit would look like:\n",
    "<img src=\"../images/qft3.png\" alt=\"Note: In order for images to show up in this jupyter notebook you need to select File => Trusted Notebook\" width=\"400 px\" align=\"center\">\n",
    "\n",
    "In QASM, it is:\n",
    "```vhdl\n",
    "qreg q[3];\n",
    "creg c[3];\n",
    "h q[0];\n",
    "cu1(pi/2) q[1],q[0];\n",
    "h q[1];\n",
    "cu1(pi/4) q[2],q[0];\n",
    "cu1(pi/2) q[2],q[1];\n",
    "h q[2];\n",
    "```\n",
    "\n",
    "In Qiskit, it is:\n",
    "```python\n",
    "q = QuantumRegister(3)\n",
    "c = ClassicalRegister(3)\n",
    "\n",
    "qft3 = QuantumCircuit(q, c)\n",
    "qft3.h(q[0])\n",
    "qft3.cu1(math.pi/2.0, q[1], q[0])\n",
    "qft3.h(q[1])\n",
    "qft3.cu1(math.pi/4.0, q[2], q[0])\n",
    "qft3.cu1(math.pi/2.0, q[2], q[1])\n",
    "qft3.h(q[2])\n",
    "```\n",
    "\n",
    "For $N=2^n$, this can be generalised, as in the `qft` function in [tools.qi](https://github.com/Qiskit/qiskit-terra/blob/master/qiskit/tools/qi/qi.py):\n",
    "```python\n",
    "def qft(circ, q, n):\n",
    "    \"\"\"n-qubit QFT on q in circ.\"\"\"\n",
    "    for j in range(n):\n",
    "        for k in range(j):\n",
    "            circ.cu1(math.pi/float(2**(j-k)), q[j], q[k])\n",
    "        circ.h(q[j])\n",
    "```"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Implementation <a id='implementation'></a>"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 1,
   "metadata": {},
   "outputs": [],
   "source": [
    "import math\n",
    "\n",
    "# importing Qiskit\n",
    "from qiskit import Aer, IBMQ\n",
    "from qiskit import QuantumRegister, ClassicalRegister, QuantumCircuit, execute\n",
    "from qiskit.backends.ibmq import least_busy\n",
    "\n",
    "# useful additional packages \n",
    "from qiskit.wrapper.jupyter import *\n",
    "from qiskit.tools.visualization import plot_histogram"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {},
   "outputs": [],
   "source": [
    "IBMQ.load_account()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "First let's define the QFT function, as well as a function that creates a state from which a QFT will return 1:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {},
   "outputs": [],
   "source": [
    "def input_state(circ, q, n):\n",
    "    \"\"\"n-qubit input state for QFT that produces output 1.\"\"\"\n",
    "    for j in range(n):\n",
    "        circ.h(q[j])\n",
    "        circ.u1(math.pi/float(2**(j)), q[j]).inverse()\n",
    "\n",
    "def qft(circ, q, n):\n",
    "    \"\"\"n-qubit QFT on q in circ.\"\"\"\n",
    "    for j in range(n):\n",
    "        for k in range(j):\n",
    "            circ.cu1(math.pi/float(2**(j-k)), q[j], q[k])\n",
    "        circ.h(q[j])"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Let's now implement a QFT on a prepared three qubit input state that should return $001$:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "OPENQASM 2.0;\n",
      "include \"qelib1.inc\";\n",
      "qreg q0[3];\n",
      "creg c0[3];\n",
      "h q0[0];\n",
      "u1(-3.14159265358979) q0[0];\n",
      "h q0[1];\n",
      "u1(-1.57079632679490) q0[1];\n",
      "h q0[2];\n",
      "u1(-0.785398163397448) q0[2];\n",
      "h q0[0];\n",
      "cu1(1.57079632679490) q0[1],q0[0];\n",
      "h q0[1];\n",
      "cu1(0.785398163397448) q0[2],q0[0];\n",
      "cu1(1.57079632679490) q0[2],q0[1];\n",
      "h q0[2];\n",
      "measure q0[0] -> c0[0];\n",
      "measure q0[1] -> c0[1];\n",
      "measure q0[2] -> c0[2];\n",
      "\n"
     ]
    }
   ],
   "source": [
    "q = QuantumRegister(3)\n",
    "c = ClassicalRegister(3)\n",
    "qft3 = QuantumCircuit(q, c)\n",
    "\n",
    "input_state(qft3, q, 3)\n",
    "qft(qft3, q, 3)\n",
    "for i in range(3):\n",
    "    qft3.measure(q[i], c[i])\n",
    "print(qft3.qasm())"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/plain": [
       "{'001': 1024}"
      ]
     },
     "execution_count": 5,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "source": [
    "# run on local simulator\n",
    "backend = Aer.get_backend(\"qasm_simulator\")\n",
    "\n",
    "simulate = execute(qft3, backend=backend, shots=1024).result()\n",
    "simulate.get_counts()"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "We indeed see that the outcome is always $001$ when we execute the code on the simulator.\n",
    "\n",
    "\n",
    "We then see how the same circuit can be executed on real-device backends."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 6,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "application/vnd.jupyter.widget-view+json": {
       "model_id": "07e166bc4b644c2fa533677a2247f577",
       "version_major": 2,
       "version_minor": 0
      },
      "text/html": [
       "<p>Failed to display Jupyter Widget of type <code>VBox</code>.</p>\n",
       "<p>\n",
       "  If you're reading this message in the Jupyter Notebook or JupyterLab Notebook, it may mean\n",
       "  that the widgets JavaScript is still loading. If this message persists, it\n",
       "  likely means that the widgets JavaScript library is either not installed or\n",
       "  not enabled. See the <a href=\"https://ipywidgets.readthedocs.io/en/stable/user_install.html\">Jupyter\n",
       "  Widgets Documentation</a> for setup instructions.\n",
       "</p>\n",
       "<p>\n",
       "  If you're reading this message in another frontend (for example, a static\n",
       "  rendering on GitHub or <a href=\"https://nbviewer.jupyter.org/\">NBViewer</a>),\n",
       "  it may mean that your frontend doesn't currently support widgets.\n",
       "</p>\n"
      ],
      "text/plain": [
       "VBox(children=(HTML(value=\"<p style='font-size:16px;'>Job Status : job is being initialized </p>\"),))"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "%%qiskit_job_status\n",
    "\n",
    "# Use the IBM Quantum Experience\n",
    "backend = least_busy(IBMQ.backends(simulator=False))\n",
    "shots = 1024\n",
    "\n",
    "job_exp = execute(qft3, backend=backend, shots=shots)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "image/png": "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\n",
      "text/plain": [
       "<matplotlib.figure.Figure at 0x29ae7b7cd68>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "results = job_exp.result()\n",
    "plot_histogram(results.get_counts())"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "We see that the highest probability outcome $001$ when we execute the code on `IBMQ device`."
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.6.4"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
